<template>
  <section class="todoapp">
    <header class="header">
      <h1>todos</h1>
      <input class="new-todo" placeholder="What needs to be done?" autofocus v-model="todoName"
        @keyup.enter="addItem" />
    </header>

    <section class="main">
      <input id="toggle-all" class="toggle-all" type="checkbox" v-model="isAll" />
      <label for="toggle-all">Mark all as complete</label>
      <ul class="todo-list">
        <li :class="{ completed: item.flag }" v-for="(item, index) in  renderList">
          <div class="view">
            <input class="toggle" type="checkbox" :checked="item.flag" @click="item.flag = !item.flag" />
            <label>{{ item.name }}</label>
            <button class="destroy" @click="delItem(item.id)"></button>
          </div>
          <input class="edit" value="Create a TodoMVC template" />
        </li>
        <!-- <li>
          <div class="view">
            <input class="toggle" type="checkbox" />
            <label>Buy a unicorn</label>
            <button class="destroy"></button>
          </div>
          <input class="edit" value="Rule the web" />
        </li> -->
      </ul>
    </section>

    <footer class="footer" v-show="isShowFooter">
      <span class="todo-count"><strong> 还剩余: {{ leftCounts }}</strong> item left</span>
      <ul class="filters">
        <!-- <li>
          <a class="selected" href="#/">All</a>
        </li>
        <li>
          <a href="#/active">Active</a>
        </li>
        <li>
          <a href="#/completed">Completed</a>
        </li> -->

        <li v-for="(item, index) in tabs" :key="index" @click="active = item">
          <a href="#/" :class="active === item ? 'selected' : ''">{{ item }}</a>
        </li>
      </ul>
      <button class="clear-completed" v-show="isShowClear" @click="clearCompleted">Clear completed</button>
    </footer>
  </section>
</template>
<!-- 

  一
列表展示
准备数据并遍历。

处理 li 上的 completed class，处理 input 上的选中状态（v-model -->


<!-- 二 删除功能
准备根据 id 删除的方法并 return（可以使用 filter 删除，或根据 id 找索引，根据索引去 splice）。

给删除按钮绑定点击事件，调用方法并传递 id。 -->



<!--  三 #添加功能
在 state 中准备状态 todoName，通过 v-model 和 input 框进行绑定，收集数据。
监听 input 框的 @keyup.enter 事件，在事件回调中进行添加的操作。
添加完毕后清空输入的内容 -->


<!--  四 底部功能
利用计算属性，统计左侧剩余数量，leftCounts。

利用计算属性，根据 state.list 的长度是否大于 0，来控制底部栏的显示与否，isShowFooter。

利用计算属性，有已完成数据时，才显示清除已完成按钮（考虑使用 some 方法），isShowClear。 -->

<!-- 五
全选反选
利用计算属性，确定全选的状态（考虑使用 every 方法），isAll。
通过 v-model 把 isAll 和 全选框进行绑定。
监听 isAll 计算属性的 set 操作，根据新值来控制所有单选按钮的状态。 -->

<!-- 六
Tab 切换
在 state 中准备 Tabs 数据（['all', 'active', 'completed']）并动态渲染出底部按钮。
在 state 中准备 active 数据，默认是 'all'，和循环时候的 tab 进行比较，如果一样则应用 selected class。
给每一个 Tab 绑定点击事件，并修改默认的 active 为当前点击的 tab。
利用计算属性，根据 active 的值，计算出 renderList，把之前循环的 list 改为 renderList。 -->

<!-- 
 七 存储本地
深度监听 () => state.list 的变化，在回调函数中对新数据进行序列化后并存储到本地。
初始化 list 的时候，从本地获取，并反序列化，没有获取到给一个默认值，防止循环的时候报错。
监听 () => state.active 的变化，回调函数中把变化后的新值存储到本地。
初始哈 active 的时候，从本地获取，没有获取到给一个默认的 'all'。 -->


<script>
import { reactive, toRefs, computed, watch } from 'vue'
const list = [
  { id: 1, name: '吃饭', flag: true },
  { id: 2, name: '睡觉', flag: false },
  { id: 3, name: '敲代码', flag: true },
];



// 删除功能
function useDelItem (state) {
  // 方式一
  const delItem = (id) => {

    alert('xxx')
    state.list = state.list.filter(item => item.id != id)
  }
  return {
    delItem
  }


  //  方式二
  // const delItem = (id) => {
  //   let currentIndex = state.list.findIndex(item => item.id == id)
  //   state.list.splice(currentIndex, 1)
  // }

  // const delItem = (id) => {
  //   state.list = state.list.reduce(( , curItem, index) => {

  //     if (curItem.id != id) {

  //       return [...pre, curItem]
  //     }
  //   }, [])
  // }

}


function useAddItem (state) {
  //  添加功能 
  const addItem = () => {
    const todoEvent = {
      id: Math.random(),
      name: state.todoName,
      flag: false
    }

    state.list.unshift(todoEvent)

    state.todoName = ''

  }

  return {
    addItem
  }

}


function useStatus (state) {
  // 左侧剩余  没完成事件 的数量
  const leftCounts = computed(() => {
    return state.list.filter(item => !item.flag).length
  })
  //  显示与隐藏  // state.list 的长度是否大于 0
  const isShowFooter = computed(() => state.list.length > 0)


  // 有已完成数据时，才显示清除已完成按钮
  // const isShowClear = computed(() => {
  //   return state.list.some(item => item.flag)
  // })

  const isShowClear = computed(() => state.list.some(item => item.flag))

  //   清除已经完成的事件 
  const clearCompleted = () => {
    state.list = state.list.filter(item => !item.flag)
  }


  return {
    clearCompleted,
    isShowClear,
    isShowFooter,
    leftCounts
  }
}


function useWatch (state) {
  //  监听所有的数据
  watch(() => state.list, (newVal) => {

    localStorage.setItem('todoList', JSON.stringify(newVal))
  }, {
    deep: true
  })

  //  监听当前的状态
  watch(() => state.active, (newVal) => {
    localStorage.setItem('active', newVal)
  }, {
    immediate: true
  })


}

function useTabsList (state) {
  const isAll = computed({
    //  判断
    get () {
      return state.list.every(item => item.flag)
    },
    //  操作 全选 
    set (newVal) {
      console.log('newVal', newVal);

      state.list.forEach(item => {
        item.flag = newVal
      })

    }
  })
  // tab切换 内容跟随
  // tabs: ['all', 'active', 'completed'],
  const renderList = computed(() => {
    if (state.active === 'all') {
      return state.list
    } else if (state.active === 'active') {

      return state.list.filter(item => !item.flag)

    } else {
      return state.list.filter(item => item.flag)
    }




  })

  return {
    isAll,
    renderList
  }


}



function useStateList () {
  const state = reactive({
    list: JSON.parse(localStorage.getItem('todoList')) || list,

    todoName: '',
    tabs: ['all', 'active', 'completed'],
    active: localStorage.getItem('active') || "all"


  })

  return {
    state
  }
}

export default {
  setup () {
    const { state } = useStateList()
    //  删除功能
    const { delItem } = useDelItem(state)
    const { addItem } = useAddItem(state)
    const { clearCompleted, isShowClear, isShowFooter, leftCounts } = useStatus(state)
    const { isAll, renderList } = useTabsList(state)
    useWatch(state)
    return {
      ...toRefs(state),
      delItem,
      addItem,
      leftCounts,
      isShowFooter,
      isShowClear,
      clearCompleted,
      isAll,
      renderList
    }
  }
}
</script>